#include <signal.h>
#include <sys/wait.h>
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <pipe.h>

#include <task.h>
#include <common.h>
#include <serial.h>


pthread_mutex_t task_mutex = PTHREAD_MUTEX_INITIALIZER;
/*
 *  函数名：monitor_tasks
 *  功能说明：监控任务状态，检测子程序是否正常退出，异常时进行重启
 *  参数：无
 *  返回值：void
 *  日期：2025年3月
 */
void monitor_tasks(void)
{
    int task_count;
    pthread_mutex_lock(&task_mutex);
    Task *tasks = get_task_list(&task_count);
    int i = 0;
    for(i = 0; i < task_count; i++)
    {
        //进程状态变化
        if(tasks[i].pid != -1)
        {
            int status;
            int needs_restart = 0;
            pid_t result = waitpid(tasks[i].pid, &status, WNOHANG);

            if(result > 0)
            {
                if(WIFEXITED(status) )   //可恢复测错误码
                {
                    int code = WEXITSTATUS(status);
                    needs_restart = (code == 101 || code == 102);   //仅特定错误码重启
                    printf("[%s] exited with status %d\n", 
                        tasks[i].name, WEXITSTATUS(status));
                }
                else if(WIFSIGNALED(status) && WTERMSIG(status) != SIGTERM)
                {
                    needs_restart = 1;  //非SIGTERM信号终止时重启
                    printf("[%s] killed by signal %d\n", 
                        tasks[i].name, WTERMSIG(status));
                }

                tasks[i].pid = -1;

                //执行重启
                if(needs_restart && tasks[i].restart_count < MAX_RESTARTS)
                {
                    tasks[i].restart_count++;
                    printf("Restarting [%s] (%d/%d)\n", 
                          tasks[i].name, tasks[i].restart_count, MAX_RESTARTS);
                    start_task(tasks[i].id, NULL);
                    if(tasks[i].restart_count >= MAX_RESTARTS)
                    {
                        printf("Restarting [%d] times overload! task restart_count >= MAX_RESTARTS\n", tasks[i].restart_count);
                    }
                }
            }
        }
    }
    pthread_mutex_unlock(&task_mutex);
}

/*
 *  函数名：task_manager_init
 *  功能说明：任务管理器初始化
 *  参数：无
 *  返回值：void
 *  日期：2025年3月
 */
void task_manager_init(void)
{

}

/*
 *  函数名：start_task
 *  功能说明：启动指定ID的任务
 *  参数：task_id - 要启动的任务ID
 *        args - 启动参数数组
 *  返回值：int - 成功返回0，失败返回-1
 *  日期：2025年3月
 */
int start_task(int task_id, char **args)
{
    printf("pthread_mutex_lock(&task_mutex)\n");
    pthread_mutex_lock(&task_mutex);
    Task *task = get_task_by_id(task_id);   //获取任务
    args[0] = (char *)task->name;
    if(task->pid != -1){
        printf("[%s] is already runing (PID:%d)\n", task->name, task->pid);
        pthread_mutex_unlock(&task_mutex);
        return -1;
    }
    
    int child_pipefd = 5;
    char child_pipefd_str[10];
    sprintf(child_pipefd_str, "%d", child_pipefd);
    //互斥访问描述符
    pipe(pipefd);
    //close(pipefd[1]);   //主进程关闭写端

    pid_t child_pid = fork();
    if(child_pid < 0)
    {
        perror("Fork failed");
        pthread_mutex_unlock(&task_mutex);
        return -1;
    }
    else if(child_pid == 0)
    {
        /* 子进程解锁task */
        pthread_mutex_unlock(&task_mutex);

        /* 重定向管道，并置is_pipe_valid为1 */
        close(pipefd[0]);   //子进程关闭读端
        if(pipefd[1] == child_pipefd)
        {
            printf_d("pipefd[1]== %d, do nothing\n", child_pipefd);
        }else{
            dup2(pipefd[1], child_pipefd); //子进程复制写端到非标准描述符
            close(pipefd[1]);
        }
        
        printf_d("pipefd[1]=%d\n", pipefd[1]);
        //close(pipefd[1]);   //子进程关闭写端
        args[2] = child_pipefd_str;      //传递描述符4作为参数
        /* execv：执行程序是以数组形式携带参数 */
        execv(task->program_path, args);
        printf_d("[Forklift] start_task execv failed\n");
        return -1;
    }
    else{
        task->pid = child_pid;
        pthread_mutex_unlock(&task_mutex);
        
        pthread_mutex_lock(&pipe_mutex);
        is_pipe_valid = 1;   //pip有效。此变量在pipe线程中共享
        pthread_mutex_unlock(&pipe_mutex);
        pthread_cond_signal(&pip_mutex_cond);
        //printf_d("[task] pthread_cond_signal pipe\n");


        printf("[%s] child process starting (PID: %d)\n", task->name, task->pid);
        return 0;
    }

}

/*
 *  函数名：stop_task
 *  功能说明：停止指定ID的任务
 *  参数：task_id - 要停止的任务ID
 *  返回值：int - 成功返回0，失败返回-1
 *  日期：2025年3月
 */
int stop_task(int task_id)
{   
    close(pipefd[0]);
    
    pthread_mutex_lock(&pipe_mutex);
    is_pipe_valid = 0;     //此变量在pipe线程中共享
    pthread_mutex_unlock(&pipe_mutex);


    // pthread_mutex_trylock(&task_mutex);
    Task *task = get_task_by_id(task_id);

    if(task->pid == -1)
    {
        printf("[%s] is not running\n", task->name);
        // pthread_mutex_unlock(&task_mutex);
        return -1;
    }

    //终止子进程
    if(kill(task->pid, SIGTERM) == -1)
    {
        perror("kill failed");
        // pthread_mutex_unlock(&task_mutex);
        return -1;
    }

    //等待子进程终止
    waitpid(task->pid, NULL, 0);
    task->pid = -1; //修改共享数据
    // pthread_mutex_unlock(&task_mutex);
    printf("[%s] stopped\n", task->name);
    return 0;
}

/*
 *  函数名：stop_all_tasks
 *  功能说明：停止所有正在运行的任务
 *  参数：无
 *  返回值：int - 成功停止的任务数量
 *  日期：2025年3月
 */
int stop_all_tasks(void)
{
    /* 释放管道 */
    close(pipefd[0]);
    close(pipefd[1]);
    pthread_mutex_lock(&pipe_mutex);
    is_pipe_valid = 0;     //pipe无效。此变量在pipe线程中共享
    pthread_mutex_unlock(&pipe_mutex);


    // pthread_mutex_lock(&task_mutex);
    int task_count;
    Task *tasks = get_task_list(&task_count);
    int stoped_count = 0;
    int i;

    /* 关闭所有子进程 */
    for(i = 0; i < task_count; i++)
    {
        if(tasks[i].pid != -1)
        {
            if(kill(tasks[i].pid, SIGTERM) == 0)
            {
                waitpid(tasks[i].pid, NULL, 0);
                tasks[i].pid = -1;
                printf("[%s] stopped\n", tasks[i].name);
                stoped_count++;
            }
        }
    }
    if(!stoped_count)
    {
        printf("[stop_all_tasks] no child process is running\n");
        
    }
    uart_send("stopped\n");
    // pthread_mutex_unlock(&task_mutex);
    return stoped_count;
}